﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using WMPLib;

namespace SFP.Audio
{
    public class AudioPlayer
    {
        private static HashSet<Sound> audios = new HashSet<Sound>();
        private static HashSet<Sound> loopAudios = new HashSet<Sound>();

        public static void play(Sound audio)
        {
            play(audio, false);
        }

        public static void play(Sound audio, bool forceReplay)
        {
            if (audio == null) return;

            if (!audios.Contains(audio))
            {
                Console.WriteLine("AUDIO_PLAYER: Added Audio");
                audios.Add(audio);
                tryPlay(audio);
            }
            else if (forceReplay)
            {
                stop(audio);
                play(audio);
            }
        }

        private static bool tryPlay(Sound audio)
        {
            if (!audio.player.playState.Equals(WMPLib.WMPPlayState.wmppsTransitioning) &&
                !audio.player.playState.Equals(WMPLib.WMPPlayState.wmppsPlaying))
            {
                Console.WriteLine("AUDIO_PLAYER: Play Audio");
                audio.player.controls.play();
                return true;
            }

            return false;
        }

        public static void loop(Sound audio)
        {
            if (!loopAudios.Contains(audio))
            {
                Console.WriteLine("AUDIO_PLAYER: Added Loop Audio");
                loopAudios.Add(audio);
                play(audio);
            }
        }

        internal static void checkLoop()
        {
            foreach (Sound audio in loopAudios)
            {
                if (tryPlay(audio)) Console.WriteLine("AUDIO_PLAYER: Looped Audio");
            }
        }

        public static void pause(Sound audio)
        {
            Console.WriteLine("AUDIO_PLAYER: Pauses Audio");
            audio.player.controls.pause();

            if (loopAudios.Contains(audio))
            {
                Console.WriteLine("AUDIO_PLAYER: Removed Loop Audio");
                loopAudios.Remove(audio);
            }
        }

        public static void pauseAll()
        {
            foreach (Sound audio in audios)
            {
                audio.player.controls.pause();
            }
        }

        public static void resumeAll()
        {
            foreach (Sound audio in audios)
            {
                tryPlay(audio);
            }
        }

        public static void stop(Sound audio)
        {
            remove(audio);
            Console.WriteLine("AUDIO_PLAYER: Stop Loop Audio");
            audio.player.controls.stop();
        }

        public static void stopAll()
        {
            foreach (Sound audio in audios)
            {
                audio.player.controls.stop();
            }
            audios.Clear();
            loopAudios.Clear();
        }

        private static void remove(Sound audio)
        {
            if (audios.Contains(audio))
            {
                Console.WriteLine("AUDIO_PLAYER: Removed Audio");
                audios.Remove(audio);
            }
            if (loopAudios.Contains(audio))
            {
                Console.WriteLine("AUDIO_PLAYER: Removed Loop Audio");
                loopAudios.Remove(audio);
            }
        }

        internal static void clean()
        {
            foreach (Sound audio in new HashSet<Sound>(audios))
            {
                if (!audio.player.playState.Equals(WMPLib.WMPPlayState.wmppsTransitioning) &&
                    !audio.player.playState.Equals(WMPLib.WMPPlayState.wmppsPlaying))
                {
                    if (!loopAudios.Contains(audio))
                    {
                        Console.WriteLine("AUDIO_PLAYER: Cleaned Audio");
                        audios.Remove(audio);
                    }
                }
            }
        }
    }
}
